"""
此文件专用于预测，且数据集已交给dataset_from_csv.py。

"""

import pandas as pd
from sklearn.preprocessing import MinMaxScaler
import numpy as np
import matplotlib.pyplot as plt
import joblib
from utility import checker as checker


plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号

class LSTMDataset_Predict:
    def __init__(self,dataset_original=None,feature_names=["None"],label_names=["None"],train_size=0,timestep=50,scaler_path=None):
       
        self.feature_names = feature_names
        self.label_names = label_names
        self.input_headers=feature_names+label_names
        self.scaler_path = scaler_path
        self.isFailed = False
        self.train_size = train_size
        self.timestep = timestep
        self.dataset_original = dataset_original
        self.x_scaler = MinMaxScaler(feature_range=(0, 1))
        self.y_scaler = MinMaxScaler(feature_range=(0, 1))
         # 一行代码就能存下来，后续随时调用
        self.csv_headers = self.dataset_original.columns.tolist()
        self._validate_headers()  # 校验列名是否正确
        # # 列名=特征名+标签名
        # print(self.feature_names)
        # 依据标题名选择数据集
        self.dataset = self.dataset_original[self.feature_names]
        # print(self.dataset)
        # 创建测试集
        self.x_predict_set = self.dataset.iloc[int(self.dataset.shape[0]*train_size):, :]    

         # 加载已有的 scaler 参数
        self.x_scaler = joblib.load(f'{self.scaler_path}/{label_names[0]}_x_scaler.pkl')
        self.y_scaler = joblib.load(f'{self.scaler_path}/{label_names[0]}_y_scaler.pkl')
            
        # 仅对测试集进行归一化处理
        self.x_predict_scaled = self.x_scaler.transform(self.x_predict_set)
       
       
 
    def _validate_headers(self) -> bool:
        """
        确保 self.input_headers 中的每个列名都能在
        self.csv_headers 里找到。全部存在则返回 True，
        否则抛出 ValueError 并列出缺失的列名。
        """
        missing = [col for col in self.feature_names if col not in self.csv_headers]
        if missing:
            raise ValueError(
            f"以下列名在原始数据中不存在：{missing}\n"
            f"➜ 请检查 feature_names / label_names 是否拼写有误，"
            f"或确认 CSV 中确实包含这些列。"
        )
        return True 
    # 定义函数，将数据转换为LSTM模型的输入输出格式，这里的timestep表示每组输入数据的时间步数
    # is_train 表示是否使用训练集，True表示使用训练集，False表示使用测试集
    def get_timeclycle_data(self):        
        # 清空数据列表  
        x_data = []
     

        xdataset = self.x_predict_scaled
            # 利用for循环将数据转换为LSTM模型的输入输出格式，提取数据中连续的timestep个数据作为输入，下一个数据作为输出
        for i in range(self.timestep, xdataset.shape[0]): 

            x_data.append(xdataset[i-self.timestep:i, :])  
                # y_data.append(ydataset[i, 0])  
            
            # 转换为 NumPy 数组  
        x_data = np.array(x_data)
            # 循环训练特征的格式应该是【样本数，时间步数，特征数】，所以需要将x_train的维度进行修改  
        x_data = np.reshape(x_data, (x_data.shape[0], self.timestep, x_data.shape[2]))  
        return x_data   
        

if __name__ == '__main__':
    pass
   
        
